package hawk.example.bookstore.po;

import static glz.hawkframework.support.ArgumentSupport.*;

import glz.hawkframework.dao.base.function.ColumnDescriptor;
import glz.hawkframework.dao.base.function.ColumnFunction;
import glz.hawkframework.dao.base.function.IRecord;
import glz.hawkframework.dao.base.function.RecordCreateDateTimeFunction;
import glz.hawkframework.dao.base.function.RecordCreateUserIdFunction;
import glz.hawkframework.dao.base.function.RecordIdFunction;
import glz.hawkframework.dao.base.function.RecordUpdateDateTimeFunction;
import glz.hawkframework.dao.base.function.RecordUpdateUserIdFunction;
import glz.hawkframework.dao.base.function.RecordVersionFunction;

import java.math.BigDecimal;
import java.math.BigInteger;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.Map;
import java.util.Optional;

/**
 * Map to table: BOOK
 */
public class BookPo implements IRecord {
    /**
     * Map to column: BOOK_ID
     */
    private BigInteger bookId;
    /**
     * ISBN
     * <p>Map to column: ISBN</p>
     */
    private String isbn;
    /**
     * 书名
     * <p>Map to column: TITLE</p>
     */
    private String title;
    /**
     * 书单价
     * <p>Map to column: PRICE</p>
     */
    private BigDecimal price;
    /**
     * 书出版日期
     * <p>Map to column: PUBLISH_DATE</p>
     */
    private LocalDate publishDate;
    /**
     * Map to column: BOOK_CATEGORY
     */
    private String bookCategory;
    /**
     * Map to column: PUBLISHER_ID
     */
    private BigInteger publisherId;
    /**
     * Map to column: CREATE_DATE_TIME
     */
    private LocalDateTime createDateTime;
    /**
     * Map to column: UPDATE_DATE_TIME
     */
    private LocalDateTime updateDateTime;
    /**
     * Map to column: DELETE_DATE_TIME
     */
    private LocalDateTime deleteDateTime;
    /**
     * Map to column: CREATE_USER_ID
     */
    private String createUserId;
    /**
     * Map to column: UPDATE_USER_ID
     */
    private String updateUserId;
    /**
     * Map to column: DELETE_USER_ID
     */
    private String deleteUserId;
    /**
     * Map to column: RECORD_VERSION
     */
    private Long recordVersion;
    /**
     * This map holds the relations between function class and column
     */
    private final Map<Class<? extends ColumnFunction>, ColumnDescriptor<?>> functionMap = new HashMap<>();

    {
        functionMap.put(RecordIdFunction.class, new ColumnDescriptor<>("BOOK_ID", "bookId", this::getBookId, null, this::setBookId));
        functionMap.put(RecordCreateDateTimeFunction.class, new ColumnDescriptor<>("CREATE_DATE_TIME", "createDateTime", this::getCreateDateTime, null, this::setCreateDateTime));
        functionMap.put(RecordUpdateDateTimeFunction.class, new ColumnDescriptor<>("UPDATE_DATE_TIME", "updateDateTime", this::getUpdateDateTime, null, this::setUpdateDateTime));
        functionMap.put(RecordCreateUserIdFunction.class, new ColumnDescriptor<>("CREATE_USER_ID", "createUserId", this::getCreateUserId, null, this::setCreateUserId));
        functionMap.put(RecordUpdateUserIdFunction.class, new ColumnDescriptor<>("UPDATE_USER_ID", "updateUserId", this::getUpdateUserId, null, this::setUpdateUserId));
        functionMap.put(RecordVersionFunction.class, new ColumnDescriptor<>("RECORD_VERSION", "recordVersion", this::getRecordVersion, null, this::setRecordVersion));
    }

    /**
     * Map to column: BOOK_ID
     */
    public BigInteger getBookId() {
        return bookId;
    }

    /**
     * Map to column: BOOK_ID
     */
    public void setBookId(BigInteger bookId) {
        this.bookId = bookId;
    }

    /**
     * Gets ISBN
     * <p>Map to column: ISBN</p>
     */
    public String getIsbn() {
        return isbn;
    }

    /**
     * Sets ISBN
     * <p>Map to column: ISBN</p>
     */
    public void setIsbn(String isbn) {
        this.isbn = isbn;
    }

    /**
     * Gets 书名
     * <p>Map to column: TITLE</p>
     */
    public String getTitle() {
        return title;
    }

    /**
     * Sets 书名
     * <p>Map to column: TITLE</p>
     */
    public void setTitle(String title) {
        this.title = title;
    }

    /**
     * Gets 书单价
     * <p>Map to column: PRICE</p>
     */
    public BigDecimal getPrice() {
        return price;
    }

    /**
     * Sets 书单价
     * <p>Map to column: PRICE</p>
     */
    public void setPrice(BigDecimal price) {
        this.price = price;
    }

    /**
     * Gets 书出版日期
     * <p>Map to column: PUBLISH_DATE</p>
     */
    public LocalDate getPublishDate() {
        return publishDate;
    }

    /**
     * Sets 书出版日期
     * <p>Map to column: PUBLISH_DATE</p>
     */
    public void setPublishDate(LocalDate publishDate) {
        this.publishDate = publishDate;
    }

    /**
     * Map to column: BOOK_CATEGORY
     */
    public String getBookCategory() {
        return bookCategory;
    }

    /**
     * Map to column: BOOK_CATEGORY
     */
    public void setBookCategory(String bookCategory) {
        this.bookCategory = bookCategory;
    }

    /**
     * Map to column: PUBLISHER_ID
     */
    public BigInteger getPublisherId() {
        return publisherId;
    }

    /**
     * Map to column: PUBLISHER_ID
     */
    public void setPublisherId(BigInteger publisherId) {
        this.publisherId = publisherId;
    }

    /**
     * Map to column: CREATE_DATE_TIME
     */
    public LocalDateTime getCreateDateTime() {
        return createDateTime;
    }

    /**
     * Map to column: CREATE_DATE_TIME
     */
    public void setCreateDateTime(LocalDateTime createDateTime) {
        this.createDateTime = createDateTime;
    }

    /**
     * Map to column: UPDATE_DATE_TIME
     */
    public LocalDateTime getUpdateDateTime() {
        return updateDateTime;
    }

    /**
     * Map to column: UPDATE_DATE_TIME
     */
    public void setUpdateDateTime(LocalDateTime updateDateTime) {
        this.updateDateTime = updateDateTime;
    }

    /**
     * Map to column: DELETE_DATE_TIME
     */
    public LocalDateTime getDeleteDateTime() {
        return deleteDateTime;
    }

    /**
     * Map to column: DELETE_DATE_TIME
     */
    public void setDeleteDateTime(LocalDateTime deleteDateTime) {
        this.deleteDateTime = deleteDateTime;
    }

    /**
     * Map to column: CREATE_USER_ID
     */
    public String getCreateUserId() {
        return createUserId;
    }

    /**
     * Map to column: CREATE_USER_ID
     */
    public void setCreateUserId(String createUserId) {
        this.createUserId = createUserId;
    }

    /**
     * Map to column: UPDATE_USER_ID
     */
    public String getUpdateUserId() {
        return updateUserId;
    }

    /**
     * Map to column: UPDATE_USER_ID
     */
    public void setUpdateUserId(String updateUserId) {
        this.updateUserId = updateUserId;
    }

    /**
     * Map to column: DELETE_USER_ID
     */
    public String getDeleteUserId() {
        return deleteUserId;
    }

    /**
     * Map to column: DELETE_USER_ID
     */
    public void setDeleteUserId(String deleteUserId) {
        this.deleteUserId = deleteUserId;
    }

    /**
     * Map to column: RECORD_VERSION
     */
    public Long getRecordVersion() {
        return recordVersion;
    }

    /**
     * Map to column: RECORD_VERSION
     */
    public void setRecordVersion(Long recordVersion) {
        this.recordVersion = recordVersion;
    }

    @Override
    public Optional<ColumnDescriptor<?>> findColumnDescriptor(Class<? extends ColumnFunction> columnFunctionClass) {
        return Optional.ofNullable(functionMap.get(argNotNull(columnFunctionClass, "columnFunctionClass")));
    }
}
